package SpEL;

import java.util.ArrayList;
import java.util.GregorianCalendar;
import java.util.List;

import org.junit.Test;
import org.springframework.expression.EvaluationContext;
import org.springframework.expression.Expression;
import org.springframework.expression.ExpressionParser;
import org.springframework.expression.spel.standard.SpelExpressionParser;
import org.springframework.expression.spel.support.StandardEvaluationContext;

public class SpELTest {

	/**
	 * 表达式求值
	 */
	@Test
	public void test1(){
		ExpressionParser parser = new SpelExpressionParser();
		Expression exp = parser.parseExpression("'Hello World'");
//		支持泛型的使用方法
//		System.out.println(exp.getValue(String.class));
		System.out.println((String)exp.getValue());
	}
	
	/**
	 * 方法调用
	 */
	@Test
	public void test2(){
		ExpressionParser parser = new SpelExpressionParser();
		Expression exp = parser.parseExpression("'Hello World'.concat('!')");
		System.out.println(exp.getValue());
	}
	
	
	/**
	 * 访问属性
	 */
	@Test
	public void test3(){
		ExpressionParser parser = new SpelExpressionParser();
		//invokes'getBytes()' 
		Expression exp = parser.parseExpression("'Hello World'.bytes");
		byte[] bytes = (byte[])exp.getValue();
		for(byte str:bytes)
			System.out.println(str);
	}
	
	/**
	 * 属性嵌套和属性设值，例如：prop1.prop2.prop3
	 */
	@Test
	public void test4(){
		ExpressionParser parser = new SpelExpressionParser();
		//invokes'getBytes().length'
		Expression exp = parser.parseExpression("'Hello World'.bytes.length");
		System.out.println((Integer)exp.getValue());
	}
	
	/**
	 * 构造器。本例使用字符串构造器而不是使用字符串蚊子
	 */
	@Test
	public void test5(){
		ExpressionParser parser = new SpelExpressionParser();
		Expression exp = parser.parseExpression("new String('hello world').toUpperCase()");
		System.out.println(exp.getValue());
	}
	
	/**
	 * 针对特定对象实例求值
	 */
	@Test
	public void test6(){
		//创建一个日历
		GregorianCalendar calendar = new GregorianCalendar();
		calendar.set(1985, 1, 14);
		
		Inventor tesla = new Inventor("Nikola tesla", calendar.getTime(), "Serbian");
		
		//取属性name的值
		ExpressionParser parser = new SpelExpressionParser();
		Expression exp = parser.parseExpression("nationality");
		System.out.println(exp.getValue(tesla));
		
		//EvaluationContext接口用来求一个解析属性，方法，域的表达式值以及帮助类型转换。
		//其即插即用实现StandardEvaluationContext使用反射机制来操作对象
		EvaluationContext context = new StandardEvaluationContext();
		//setRootObject指定求值根对象或传递根对象到构造器
		((StandardEvaluationContext) context).setRootObject(tesla);
		System.out.println((String)exp.getValue(context));
		
		
		exp = parser.parseExpression("name=='Nikola tesla'");
		System.out.println(exp.getValue(context,Boolean.class));	
	}
	
	/**
	 * 类型转换
	 */
	@Test
	public void test7(){
		class Simple{  
			public List<Boolean> booleanList= new ArrayList<Boolean>();  
		}
		Simple simple = new Simple();
		simple.booleanList.add(true);
		StandardEvaluationContext simpleContext= new StandardEvaluationContext(simple);  
		
		ExpressionParser parser = new SpelExpressionParser();
		parser.parseExpression("booleanList[0]").setValue(simpleContext, "false");  
		System.out.println(simple.booleanList.get(0)); 
	}
	

}
